﻿/*                       NOTICE
 * 
 * This software was produced for the U. S. Government
 * under Contract No. FA8721-10-C-0001, and is
 * subject to the Rights in Noncommercial Computer Software
 * and Noncommercial Computer Software Documentation Clause
 * (DFARS) 252.227-7014 (JUN 1995)
 * 
 * Approved for Public Release: 11-2435
 * © 2011 The MITRE Corporation. All Rights Reserved. 
 * 
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 * 
 * http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */



using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using InputManager;
using GestureListenerClient.Services.Delegates;
using GestureListenerClient.Services;
using System.Collections;
using System.Threading;
using System.IO;

namespace GestureControlOfWindowsForm
{
    public partial class ControlForm : Form
    {
       
        public int zoomSpeed = 1;

        public int offsetX = 0;
        public int offsetY = 0;
        private int adjustmentOffsetX;
        private int adjustmentOffsetY;
        private int screenOffsetX = Screen.AllScreens[0].Bounds.Location.X;
        private int screenOffsetY = Screen.AllScreens[0].Bounds.Location.Y;
        public int height = Screen.AllScreens[0].Bounds.Size.Height;
        public int width = Screen.AllScreens[0].Bounds.Size.Width;

        private ArrayList movePoints;
        private DateTime lastMoveCapture;
        private Dictionary<string, Type> applicationProfiles = new Dictionary<string,Type>();
        private GestureClient listener;

        private string configFile;

        public ControlForm(string configFile, string defaultProfile)
        {
            InitializeComponent();

            this.configFile = configFile;
            if (configFile != null)
            {
                parseConfigSettings();
                listener = new GestureClient("WindowsControl" + Guid.NewGuid().ToString(), configFile);
            }

            
            adjustmentOffsetX = (int)adjustXOffsetSpinner.Value;
            adjustmentOffsetY = (int)adjustYOffsetSpinner.Value;

            if (Screen.AllScreens.Length == 1)
                secondaryRadio.Enabled = false;
            else
            {
                Rectangle bounds = Screen.AllScreens[1].Bounds;
                offsetX = (screenOffsetX = bounds.Location.X) + adjustmentOffsetX;
                offsetY = (screenOffsetY = bounds.Location.Y) + adjustmentOffsetY;
                width = bounds.Size.Width;
                height = bounds.Size.Height;
            }

            addProfiles();
            applicationProfileBox.Items.AddRange(applicationProfiles.Keys.ToArray());
            foreach (Type type in applicationProfiles.Values)
                if (!typeof(ApplicationProfile).IsAssignableFrom(type))
                    throw new ArgumentException("One of the types isn't an ApplicationProfile");

            if (defaultProfile != null)
            {
                defaultProfile = defaultProfile.Replace('_', ' ');
                Type appType = applicationProfiles[defaultProfile];
                object[] parameters = new object[] { this };
                ApplicationProfile profile = Activator.CreateInstance(appType, parameters) as ApplicationProfile;
                profile.setListener(listener);
                applicationProfileBox.Text = defaultProfile;
            }

            //Thread oThread = new Thread(new ThreadStart(cleanUpGestures));
            //oThread.Start();
        }

        /// <summary>
        /// Add any ApplicationProfile classes to the system here.
        /// </summary>
        public void addProfiles()
        {
            applicationProfiles.Add("Google Earth", typeof(GoogleEarthProfile));
            applicationProfiles.Add("WorldWind", typeof(WorldWindProfile));
            applicationProfiles.Add("MOVINT", typeof(MOVINTProfile));
        }

        // Grabs the config parameters out of the given config file.
        protected void parseConfigSettings()
        {
            using (StreamReader reader = new StreamReader(configFile))
            {
                Dictionary<string, string> settingLookup = new Dictionary<string, string>();
                string line = reader.ReadLine();
                while (line != null)
                {
                    string[] elements = line.Split(':');
                    if (elements.Length > 1)
                        settingLookup.Add(elements[0], elements[1].TrimStart(' '));
                    line = reader.ReadLine();
                }

            


                reader.Close();
            }
        }

        
        private void primaryRadio_CheckedChanged(object sender, EventArgs e)
        {
            if (primaryRadio.Checked)
            {
                Rectangle bounds = Screen.AllScreens[0].Bounds;
                offsetX = (screenOffsetX = bounds.Location.X) + adjustmentOffsetX;
                offsetY = (screenOffsetY = bounds.Location.Y) + adjustmentOffsetY;
                width = bounds.Size.Width;
                height = bounds.Size.Height;
            }
            else
            {
                Rectangle bounds = Screen.AllScreens[1].Bounds;
                offsetX = (screenOffsetX = bounds.Location.X) + adjustmentOffsetX;
                offsetY = (screenOffsetY = bounds.Location.Y) + adjustmentOffsetY;
                width = bounds.Size.Width;
                height = bounds.Size.Height;
            }
        }

        private void applicationProfileBox_SelectedIndexChanged(object sender, EventArgs e)
        {
            listener.unregisterAll();
            Type appType = applicationProfiles[applicationProfileBox.Text];
            object[] parameters = new object[] { this };
            ApplicationProfile profile = Activator.CreateInstance(appType, parameters) as ApplicationProfile;
            profile.setListener(listener);
        }

        private void adjustXOffsetSpinner_ValueChanged(object sender, EventArgs e)
        {
            offsetX = screenOffsetX + (adjustmentOffsetX = (int)adjustXOffsetSpinner.Value);
        }

        private void adjustYOffsetSpinner_ValueChanged(object sender, EventArgs e)
        {
            offsetY = screenOffsetY + (adjustmentOffsetY = (int)adjustYOffsetSpinner.Value);
        }

        public bool isYInverted()
        {
            return invertYBox.Checked;
        }

        private void zoomSlider_Scroll(object sender, EventArgs e)
        {
            zoomSpeed = zoomSlider.Value;
        }
    }
}
